# -*- coding: utf-8 -*-

import sys
import locale
import time
import functools
import twitter
import redis
from login_twitter import login

#faz consultas RestFull dinamicas
def fazRequisicaoTwitter(twitterFunction, max_errors=3, *args, **kwArgs): 
    error_count = 0

    while True:
        try:
            return twitterFunction(*args, **kwArgs)
        except twitter.api.TwitterHTTPError, e:
            print "TwitterHTTPError encontrado. Continuando."
        except URLError, e:
            error_count += 1
            print >> sys.stderr, "URLError encontrado. Continuando."
            if error_count > max_errors:
                print >> sys.stderr, "Muitos erros consecutivos ... resgatando."
                raise



def getAmigosOuSeguidoresViaRequest(
    func,
    key_name,
    t, # conexão Twitter 
    r, # conexão Redis 
    screen_name=None,
    limit=10000,
    ):

    cursor = -1

    result = []
    while cursor != 0:
        response = fazRequisicaoTwitter(func, screen_name=screen_name, cursor=cursor)
        for _id in response['ids']:
            result.append(_id)
            r.sadd(getRedisChaveValor(screen_name, key_name), _id)

        cursor = response['next_cursor']
        scard = r.scard(getRedisChaveValor(screen_name, key_name))
        print >> sys.stderr, 'Existem %s %s  para %s' % (scard,key_name, screen_name)
        if scard >= limit:
            break

    return result


def getRedisChaveValor(screen_name, key_name):
    return 'screen_name$' + screen_name + '$' + key_name


SCREEN_NAME = "dani_dauster"

if len(sys.argv) > 2:
    MAXINT = int(sys.argv[2])
else:
    MAXINT = sys.maxint

# Para formatação do dados do tipo numero
locale.setlocale(locale.LC_ALL, '')  

# estabelece conexão com twitter

t = login()

# conexão default do redis
r = redis.Redis()  

# Capturando amigos 
# Capturando seguidores

getFriends = functools.partial(getAmigosOuSeguidoresViaRequest, 
                               t.friends.ids, 'friend_ids', t, r)

getFollowers = functools.partial(getAmigosOuSeguidoresViaRequest,
                                 t.followers.ids, 'follower_ids', t, r)

screen_name = SCREEN_NAME

# get the data

print >> sys.stderr, 'Total de amigos para  %s...' % (screen_name, )
getFriends(screen_name, limit=MAXINT)

print >> sys.stderr, 'Total de seguidores para  %s...' % (screen_name, )
getFollowers(screen_name, limit=MAXINT)

# Redis utilizar para calcular os números
# scard retorna a cardinalidade do conjuto
# sdiffstore calcula a diferença dos conjuntos
# sinterstore calcula a interseção dos conjuntos

n_friends = r.scard(getRedisChaveValor(screen_name, 'friend_ids'))

n_followers = r.scard(getRedisChaveValor(screen_name, 'follower_ids'))

n_friends_diff_followers = r.sdiffstore('temp',
                                        [getRedisChaveValor(screen_name,
                                        'friend_ids'),
                                        getRedisChaveValor(screen_name,
                                        'follower_ids')])
r.delete('temp')

n_followers_diff_friends = r.sdiffstore('temp',
                                        [getRedisChaveValor(screen_name,
                                        'follower_ids'),
                                        getRedisChaveValor(screen_name,
                                        'friend_ids')])
r.delete('temp')

n_friends_inter_followers = r.sinterstore('temp',
        [getRedisChaveValor(screen_name, 'follower_ids'),
        getRedisChaveValor(screen_name, 'friend_ids')])
r.delete('temp')

print '%s esta seguindo %s' % (screen_name, locale.format('%d', n_friends, True))
print '%s esta sendo seguido(a) por %s' % (screen_name, locale.format('%d',
                                      n_followers, True))
print '%s de %s nao estao seguindo %s' % (locale.format('%d',
        n_friends_diff_followers, True), locale.format('%d', n_friends, True),
        screen_name)
print '%s de %s sao esta sendo seguido(a) por %s' % (locale.format('%d',
        n_followers_diff_friends, True), locale.format('%d', n_followers, True),
        screen_name)
print '%s tem %s amigos mutuos ou em comum' \
    % (screen_name, locale.format('%d', n_friends_inter_followers, True))

